/*
 * @Description: mysql 连接池
 * @Autor: HuiSir<www.zuifengyun.com>
 * @Date: 2022-05-30 10:08:20
 * @LastEditTime: 2022-07-25 10:57:25
 */
import mysql from 'mysql'
import useConfig from './useConfig.js'
import log from './useLog.js'
import { IDatabase } from './useConfig.js'

export class Pool {
    static instance: Pool
    pool: mysql.Pool

    constructor(dbConfig: IDatabase) {
        this.pool = mysql.createPool(dbConfig)
        log.info('Mysql 连接池初始化成功')
    }

    // 单例
    static getInstance(): Pool {
        if (!Pool.instance) {
            const { db } = useConfig()
            // 无配置项报错
            if (!db) {
                throw new Error(`Config Error: 'db' is not defined! Please check the 'application.yml' configuration item.`)
            }
            Pool.instance = new Pool(db)
        }
        return Pool.instance;
    }

    /**
     * 获取连接
     * 查询后记得释放`connection.release()`
     */
    async getConn(): Promise<mysql.PoolConnection> {
        return await new Promise((resolve, reject) => {
            this.pool.getConnection((err, connection) => {
                // not connected!
                if (err) {
                    reject(err);
                    return
                }
                resolve(connection)
            })
        })
    }

    /**
     * 关闭所有
     * 使用完池后，您必须结束所有连接，否则 Node.js 事件循环将保持活动状态，直到 MySQL 服务器关闭连接。
     */
    async closeAll(): Promise<void> {
        return await new Promise((resolve, reject) => {
            this.pool.end((err) => {
                if (err) {
                    reject(err);
                    return
                }
                // all connections in the pool have ended
                resolve()
            });
        })
    }
}


// 单例
export default Pool.getInstance